package com.winning.sx.microframework.common.util;

import net.sf.json.JSONObject;
import org.apache.commons.lang.StringEscapeUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.http.HttpResponse;
import org.apache.http.HttpStatus;
import org.apache.http.NameValuePair;
import org.apache.http.client.HttpClient;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.conn.ClientConnectionManager;
import org.apache.http.conn.scheme.Scheme;
import org.apache.http.conn.scheme.SchemeRegistry;
import org.apache.http.conn.ssl.SSLSocketFactory;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;

import javax.net.ssl.SSLContext;
import javax.net.ssl.X509TrustManager;
import java.io.*;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.security.SecureRandom;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.util.*;

public class HttpRequestUtil {
	private static Log logger = LogFactory.getLog(HttpRequestUtil.class); // 日志记录
	private static final String ENCODING = "UTF-8";


	/**
	 * httpPost
	 * 
	 * @param url
	 *            路径
	 * @return
	 */
	public static JSONObject httpPost(String url, Map<String, String> paramMap) {
		return httpPost(url, paramMap, false);
	}

	/**
	 * post请求
	 * 
	 * @param url
	 *            url地址
	
	 *            参数
	 * @param noNeedResponse
	 *            不需要返回结果
	 * @return
	 */
	public static JSONObject httpPost(String url, Map<String, String> paramMap, boolean noNeedResponse) {
		logger.info("PostURL: " + url);
//		logger.info("param: " + paramMap.toString());
		// post请求返回结果
		CloseableHttpClient httpClient = HttpClients.createDefault();
		JSONObject jsonResult = new JSONObject();
		HttpPost method = new HttpPost(url);
		RequestConfig requestConfig = RequestConfig.custom().setSocketTimeout(2000).setConnectTimeout(2000).build();//设置请求和传输超时时间
		method.setConfig(requestConfig);
		try {
			if (null != paramMap) {
				// 解决中文乱码问题
				UrlEncodedFormEntity entity = new UrlEncodedFormEntity(map2List(paramMap), "utf-8");
				method.setEntity(entity);
			}
			HttpResponse result = httpClient.execute(method);
			url = URLDecoder.decode(url, ENCODING);
			/** 请求发送成功，并得到响应 **/
			if (result.getStatusLine().getStatusCode() == 200) {
//				String str = "";
				try {
					/** 读取服务器返回过来的json字符串数据 **/
					if (noNeedResponse) {
						jsonResult.put("code","200");
						return jsonResult;
					}
					InputStream inStream =result.getEntity().getContent();
					BufferedReader reader = new BufferedReader(new InputStreamReader(inStream, "utf-8"));//请注意这里的编码 
					StringBuilder strber = new StringBuilder();
					String line = null;
					while ((line = reader.readLine()) != null)
						strber.append(line);
					inStream.close();
//					str = EntityUtils.toString(result.getEntity());
					/** 把json字符串转换成json对象 **/
					jsonResult = JSONObject.fromObject(strber.toString());
				} catch (Exception e) {
					logger.error("post请求提交失败:" + url, e);
				}
			}else{
				jsonResult.put("code",result.getStatusLine().getStatusCode());
			}
		} catch (IOException e) {
			jsonResult.put("code","8888");
			jsonResult.put("msg","网络异常");
			logger.error("post请求提交失败:" + url, e);
		}
//		logger.info("ret: " + jsonResult);
		return jsonResult;
	}

	private static List<NameValuePair> map2List(Map<String, String> params) {
		List<NameValuePair> nvps = new ArrayList<NameValuePair>();

		Set<String> keySet = params.keySet();
		for (String key : keySet) {
			nvps.add(new BasicNameValuePair(key, params.get(key)));
		}
		return nvps;
	}

	/**
	 * 发送get请求
	 * 
	 * @param url
	 *            路径
	 * @return
	 */
	public static JSONObject httpGet(String url) {
		// get请求返回结果
		JSONObject jsonResult = null;
		try {
			// CloseableHttpClient client = HttpClients.createDefault();//旧的方法
			HttpClient client = getSecuredHttpClient(new DefaultHttpClient());
			// 发送get请求
			logger.info("send getTo:" + url);
			// ？ %3F
			//
			// & %26
			//
			// | %124
			//
			// = %3D
			//
			// # %23
			//
			// / %2F
			//
			// + %2B
			//
			// % %25
			url = url.trim();
			// url = url.replaceAll("&", "%26");
			// url = url.replaceAll("=", "%3D");
			// url = url.replaceAll("/", "%2F");
			// String[] urls= url.split("");
			HttpGet request = new HttpGet(url);
			RequestConfig requestConfig = RequestConfig.custom().setSocketTimeout(2000).setConnectTimeout(2000).build();//设置请求和传输超时时间
			request.setConfig(requestConfig);
			HttpResponse response = client.execute(request);
			logger.info("response:" + response.getStatusLine().getStatusCode());
			/** 请求发送成功，并得到响应 **/
			if (response.getStatusLine().getStatusCode() == HttpStatus.SC_OK) {
				/** 读取服务器返回过来的json字符串数据 **/
				String strResult = EntityUtils.toString(response.getEntity());
				/** 把json字符串转换成json对象 **/
				strResult = StringUtil.cleanWinningJSON(strResult);

				strResult = StringEscapeUtils.unescapeJava(strResult);

				jsonResult = JSONObject.fromObject(strResult);
				url = URLDecoder.decode(url, ENCODING);
			} else {
				logger.error("get请求提交失败:" + url);
			}
		} catch (IOException e) {
			logger.error("get请求提交失败:" + url, e);
		}
		return jsonResult;
	}

	public static String mapToFormData(Map<String, String> params, boolean isURLEncoder)
			throws UnsupportedEncodingException {
		List<String> keys = new ArrayList<String>(params.keySet());
		Collections.sort(keys);
		String prestr = "";
		try {
			for (int i = 0; i < keys.size(); i++) {
				String key = keys.get(i);
				String value = String.valueOf(params.get(key));
				if (value == null || value.equals("null")) {
					value = "";
				}
				if (isURLEncoder && value != null)
					value = URLEncoder.encode(value, "UTF-8");
				if (i == keys.size() - 1) {// 拼接时，不包括最后一个&字符
					prestr = prestr + key + "=" + value;
				} else {
					prestr = prestr + key + "=" + value + "&";
				}
			}
		}catch(Exception e){
			e.printStackTrace();
		}
		return prestr;
	}

	/**
	 * 发送get请求
	 * 
	 * @param url
	 *            路径
	 * @return
	 */
	public static JSONObject httpGet(String url, Map param, boolean isURLEncoder) {
		// get请求返回结果
		JSONObject jsonResult = null;
		try {
			url += ("?" + mapToFormData(param, isURLEncoder));
			// CloseableHttpClient client = HttpClients.createDefault();//旧的方法
			HttpClient client = getSecuredHttpClient(new DefaultHttpClient());
			// 发送get请求
			logger.info("send getTo:" + url);
			// ？ %3F
			//
			// & %26
			//
			// | %124
			//
			// = %3D
			//
			// # %23
			//
			// / %2F
			//
			// + %2B
			//
			// % %25
			url = url.trim();
			// url = url.replaceAll("&", "%26");
			// url = url.replaceAll("=", "%3D");
			// url = url.replaceAll("/", "%2F");
			// String[] urls= url.split("");
			try {
				HttpGet request = new HttpGet(url);
				RequestConfig requestConfig = RequestConfig.custom().setSocketTimeout(100).setConnectTimeout(100).build();//设置请求和传输超时时间
				request.setConfig(requestConfig);
				HttpResponse response = client.execute(request);
				logger.info("response:" + response.getStatusLine().getStatusCode());
				/** 请求发送成功，并得到响应 **/
				if (response.getStatusLine().getStatusCode() == HttpStatus.SC_OK) {
					/** 读取服务器返回过来的json字符串数据 **/
					String strResult = EntityUtils.toString(response.getEntity());
					/*** 清理json字符串 **/
					strResult = StringUtil.cleanWinningJSON(strResult);
					strResult = StringEscapeUtils.unescapeJava(strResult);
					/** 把json字符串转换成json对象 **/

					jsonResult = JSONObject.fromObject(strResult);

					url = URLDecoder.decode(url, ENCODING);
				} else {
					logger.error("get请求提交失败:" + url);
				}
			} catch (Exception e) {
				return null;
			}
		} catch (IOException e) {
			logger.error("get请求提交失败:" + url, e);
		}
		return jsonResult;
	}


	/**
	 * 重新包装httpclient对象，忽略证书验证
	 * 
	 * @param httpClient
	 * @return
	 * @author:Administrator
	 * @date:2014-9-2
	 */
	private static DefaultHttpClient getSecuredHttpClient(HttpClient httpClient) {
		final X509Certificate[] _AcceptedIssuers = new X509Certificate[] {};
		try {
			SSLContext ctx = SSLContext.getInstance("TLS");
			X509TrustManager tm = new X509TrustManager() {
				@Override
				public X509Certificate[] getAcceptedIssuers() {
					return _AcceptedIssuers;
				}

				@Override
				public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException {
				}

				@Override
				public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException {
				}
			};
			ctx.init(null, new javax.net.ssl.TrustManager[] { tm }, new SecureRandom());
			SSLSocketFactory ssf = new SSLSocketFactory(ctx, SSLSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER);
			ClientConnectionManager ccm = httpClient.getConnectionManager();
			SchemeRegistry sr = ccm.getSchemeRegistry();
			sr.register(new Scheme("https", 443, ssf));
			return new DefaultHttpClient(ccm, httpClient.getParams());
		} catch (Exception e) {
			System.out.println("=====:=====");
			e.printStackTrace();
		}
		return null;
	}
}
